﻿namespace Cos.Module.CMS.NHibernate
{
    using System;
    using System.Collections.Generic;
    using System.Linq;

    using Cos.Core.Model.Content;
    using Cos.Core.NHibernate;
    using Cos.Core.NHibernate.Util;
    using Cos.Module.CMS.Data;

    using global::NHibernate;
    using global::NHibernate.Criterion;

    public class ElementRepository:  RepositoryBase, IElementRepository
    {
        public ElementRepository(ISessionFactory sessionFactory) 
            : base(sessionFactory)
        {
        }

        public Core.Model.Content.Element GetElement(int elementId)
        {
            var element = this.CurrentSession.Get<ElementDataModel>(elementId);

            if (element == null)
            {
                return null;
            }

            return element.ToElement();
        }

        public Core.Model.Content.Element GetElement(string cultureCode, int navId, int partId)
        {
            var query =
               this.CurrentSession.CreateSQLQuery(" SELECT " + " e.* " + " FROM " + " Elements AS e " +
                                                  " JOIN Page AS p ON p.NavId = :navId AND p.CultureCode = :cultureCode AND e.PageId = p.PageId " +
                                                  " WHERE e.PartId = :partId ");
            
            query.SetInt32("navId", navId);
            query.SetString("cultureCode", cultureCode);
            query.SetInt32("partId", partId);
            query.AddEntity(typeof(ElementDataModel));

            var element = query.UniqueResult<ElementDataModel>();
            
            if (element == null)
            {
                return null;
            }

            return element.ToElement();
        }

        public IEnumerable<Core.Model.Content.Element> GetElements(int pageId)
        {
            return this.CurrentSession.CreateCriteria<ElementDataModel>().Add(Restrictions.Eq("PageId", pageId)).List<ElementDataModel>().Select(CMSModelConverter.ToElement);
        }

        public IEnumerable<Core.Model.Content.Element> GetElements(string cultureCode, int navId)
        {
            throw new NotImplementedException();
        }

        public Core.Model.Content.Element SaveElement(Element element)
        {
            var elementDataModel = this.CurrentSession.Get<ElementDataModel>(element.ElementId).ToElementDataModel(element);
            
            this.CurrentSession.SaveOrUpdate(elementDataModel);

            this.CurrentSession.Flush();

            return elementDataModel.ToElement();
        }

        public void DeleteElement(int elementId)
        {
            this.CurrentSession.Delete(elementId);
        }
    }
}
